{
 "cells": [
  {
   "cell_type": "markdown",
   "id": "d3f92915-80cc-4681-b132-6bfb7c37a9a0",
   "metadata": {},
   "source": [
    "# Matplotlib 示例"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "ffe92d1e-cff4-484b-85c0-cdb5455d142d",
   "metadata": {},
   "source": [
    "## 基础用法"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "fe523ac6-4980-4700-9e2d-3552f918a37a",
   "metadata": {},
   "source": [
    "### 创建Figure（画布）"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "fe17f5c6-d009-4bc5-9501-9c0c71763dca",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "\n",
    "# 创建画布：尺寸8x6英寸，分辨率200dpi，背景色浅灰色\n",
    "fig = plt.figure(figsize=(8, 6), dpi=200, facecolor='lightgrey')\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "5c7b0eca-3a79-428e-99ba-dbfe7e4832da",
   "metadata": {},
   "source": [
    "### 创建Axes（子图）"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "6aaa04d1-ec94-4cb3-a4af-3f4929875ad1",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "# 创建2x2子图网格，共享x轴\n",
    "fig, axs = plt.subplots(2, 2, figsize=(12, 8), sharex=True, \n",
    "                        gridspec_kw={'wspace':0.3, 'hspace':0.4})\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "2de80c26-80e3-4703-951d-c34f4fe736a5",
   "metadata": {},
   "source": [
    "### 设定X轴、Y轴和刻度"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "df6021b0-4440-4f73-9de6-cd18fb1ebf65",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "y = np.sin(x)\n",
    "\n",
    "plt.plot(x, y)\n",
    "\n",
    "plt.xlim(-1, 11) # 设置x轴范围\n",
    "plt.ylim(-1.5, 1.5) # 设置y轴范围\n",
    "\n",
    "plt.xticks(np.arange(0, 11, 2)) # 设置x轴刻度\n",
    "plt.yticks([-1, 0, 1], ['Min', 'Zero', 'Max']) # 设置y轴刻度及标签\n",
    "\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "8614e79b-74d6-49ca-b3d7-6d577c5ca6d7",
   "metadata": {},
   "source": [
    "### 给上图添加标题与轴标签"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "e9c89a70-98f9-470f-b835-5c5bd88c30d4",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "y = np.sin(x)\n",
    "\n",
    "plt.plot(x, y)\n",
    "\n",
    "plt.xlim(-1, 11) # 设置x轴范围\n",
    "plt.ylim(-1.5, 1.5) # 设置y轴范围\n",
    "\n",
    "plt.xticks(np.arange(0, 11, 2)) # 设置x轴刻度\n",
    "plt.yticks([-1, 0, 1], ['Min', 'Zero', 'Max']) # 设置y轴刻度及标签\n",
    "\n",
    "plt.title(\"Custom Axis Limits and Ticks\")\n",
    "plt.xlabel(\"X-axis\")\n",
    "plt.ylabel(\"Y-axis\")\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "8a6eba8d-649e-4569-924f-b4036ebf875e",
   "metadata": {},
   "source": [
    "### 图例"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "f80d474c-c183-40f7-b2fa-3a22ae14fb0b",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "y = np.sin(x)\n",
    "\n",
    "plt.plot(x, y, label=\"Sine Function\") # 需要添加label，它被legend()所依赖\n",
    "\n",
    "plt.xlim(-1, 11) # 设置x轴范围\n",
    "plt.ylim(-1.5, 1.5) # 设置y轴范围\n",
    "\n",
    "plt.xticks(np.arange(0, 11, 2)) # 设置x轴刻度\n",
    "plt.yticks([-1, 0, 1], ['Min', 'Zero', 'Max']) # 设置y轴刻度及标签\n",
    "\n",
    "plt.legend(loc='upper right', shadow=True, fontsize='medium') # 定制图例位置、阴影、字体大小\n",
    "\n",
    "plt.title(\"Custom Legend\")\n",
    "plt.xlabel(\"X-axis\")\n",
    "plt.ylabel(\"Y-axis\")\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "2d8f21c7-3dbc-42b0-9651-a01f3fa4685e",
   "metadata": {},
   "source": [
    "### 自定义拆线图图形风格"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "f33f6278-715f-48d6-b87e-01b0a1d506e9",
   "metadata": {},
   "source": [
    "#### PyPlot风格"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "971a9dcd-894f-44d6-b8e3-830546acd41c",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "\n",
    "plt.plot(x, np.sin(x), color='red', linestyle='--', marker='o', markersize=4, label='Sine')\n",
    "plt.plot(x, np.cos(x), color='blue', linestyle='-.', marker='x', markersize=4, label='Cosine')\n",
    "\n",
    "plt.title(\"Sine and Cosine Waves\")\n",
    "plt.xlabel(\"X-axis\")\n",
    "plt.ylabel(\"Y-axis\")\n",
    "plt.legend() # 显示图例\n",
    "plt.grid(True) # 添加网格线\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "1a71791b-8bb4-4ca0-99ec-29eb2e3326f6",
   "metadata": {},
   "source": [
    "#### 面向对象风格"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "b160756c-30bf-4b5d-8d3e-61ada7333a29",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "\n",
    "# 创建一个 Figure 和一个 Axes 对象\n",
    "fig, ax = plt.subplots(figsize=(8, 4)) # fig 是 Figure 对象，ax 是 Axes 对象\n",
    "\n",
    "# 在 ax 上绘制数据\n",
    "ax.plot(x, np.sin(x), color='red', linestyle='--', marker='o', markersize=4, label='Sine')\n",
    "ax.plot(x, np.cos(x), color='blue', linestyle='-.', marker='x', markersize=4, label='Cosine')\n",
    "\n",
    "# 使用 Axes 对象的方法设置标题、标签等\n",
    "ax.set_title(\"Sine and Cosine Waves\")\n",
    "ax.set_xlabel(\"X-axis\")\n",
    "ax.set_ylabel(\"Y-axis\")\n",
    "ax.legend()\n",
    "ax.grid(True)\n",
    "\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "4fed74b7-4135-48cc-bcc3-abb727bd0cfa",
   "metadata": {},
   "source": [
    "### 散点图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "a929cd33-ef53-4ec7-867f-6ad8b1f23337",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "np.random.seed(0)\n",
    "x = np.random.rand(50) * 10\n",
    "y = np.random.rand(50) * 10\n",
    "colors = np.random.rand(50)\n",
    "sizes = np.random.rand(50) * 100 + 50 # 随机生成大小\n",
    "\n",
    "plt.scatter(x, y, c=colors, s=sizes, alpha=0.7, cmap='viridis')\n",
    "plt.colorbar(label='Color Intensity') # 添加颜色条\n",
    "plt.title(\"Scatter Plot\")\n",
    "plt.xlabel(\"X-value\")\n",
    "plt.ylabel(\"Y-value\")\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "aacf4052-7be9-4225-9ab8-751ac9dae9b4",
   "metadata": {},
   "source": [
    "### 直方图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "2b7aa5ab-e8fe-435f-a3dc-a40813f80a6a",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "# 准备数据 (正态分布的随机数)\n",
    "data = np.random.randn(1000)\n",
    "\n",
    "# 绘制直方图\n",
    "plt.hist(data, bins=30, color='skyblue', edgecolor='black', alpha=0.8, density=False)\n",
    "\n",
    "# 添加标题和标签\n",
    "plt.title(\"Histogram of Normally Distributed Data\")\n",
    "plt.xlabel(\"Value Range\")\n",
    "plt.ylabel(\"Frequency\")\n",
    "plt.grid(axis='y', alpha=0.75) # 只显示Y轴网格\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "8b722da1-2aa1-4407-b103-05a0e52fb7a0",
   "metadata": {},
   "source": [
    "### 柱状图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "dc4da6dd-53af-4b6d-93ed-fa8536bd0c76",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "# 准备数据\n",
    "products = ['Product A', 'Product B', 'Product C', 'Product D']\n",
    "sales = [150, 220, 180, 90]\n",
    "colors = ['lightcoral', 'skyblue', 'lightgreen', 'gold']\n",
    "\n",
    "# 绘制柱状图\n",
    "plt.bar(products, sales, color=colors, width=0.7)\n",
    "\n",
    "# 添加标题和标签\n",
    "plt.title(\"Product Sales Comparison\")\n",
    "plt.xlabel(\"Product Category\")\n",
    "plt.ylabel(\"Sales Amount ($)\")\n",
    "plt.ylim(0, 250) # 设置Y轴范围\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "a664522d-bbb1-4b6f-b212-a952eab290db",
   "metadata": {},
   "source": [
    "### 饼图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "95f0a967-9d03-4a80-a5e6-941ecc01c67a",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "\n",
    "# 准备数据\n",
    "labels = ['Apples', 'Bananas', 'Oranges', 'Grapes']\n",
    "sizes = [30, 25, 20, 25] # 比例\n",
    "explode = (0, 0.1, 0, 0) # 突出显示第二个扇形 (Bananas)\n",
    "\n",
    "# 绘制饼图\n",
    "plt.pie(sizes, explode=explode, labels=labels, autopct='%1.1f%%',\n",
    "        shadow=True, startangle=140, colors=['#ff9999','#66b3ff','#99ff99','#ffcc99'])\n",
    "\n",
    "plt.axis('equal') # 确保饼图是圆形\n",
    "plt.title(\"User's Favorite Fruits Distribution\")\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "3abb13fb-df11-48d8-a6b5-4bf842e22205",
   "metadata": {},
   "source": [
    "## 子图"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "aaea1f68-f530-4e33-881a-6d836d4dd0b5",
   "metadata": {},
   "source": [
    "### Pyplot风格的子图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "0bb00faa-0ed1-432f-a00c-7cfc4d417671",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "\n",
    "plt.figure(figsize=(10, 5)) # 设置Figure大小\n",
    "\n",
    "plt.subplot(1, 2, 1) # 1行2列的第一个子图\n",
    "plt.plot(x, np.sin(x), color='red', label=\"Sine Fucntion\")\n",
    "plt.legend(loc='lower left', fontsize='medium')\n",
    "plt.title(\"Sine Wave\")\n",
    "\n",
    "plt.subplot(1, 2, 2) # 1行2列的第二个子图\n",
    "plt.plot(x, np.cos(x), color='blue', label=\"cosine Fucntion\")\n",
    "plt.legend(loc='upper left', fontsize='medium')\n",
    "plt.title(\"Cosine Wave\")\n",
    "\n",
    "plt.tight_layout() # 自动调整子图间距，避免重叠\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "a51ca942-f8e3-4c9d-82d5-3a60d56de05e",
   "metadata": {},
   "source": [
    "### Pyplot风格子图2：一次创建所有子图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "442490eb-ccea-404d-b878-83997f07a9f7",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "\n",
    "# 使用 plt.subplots() 创建一个 Figure 和一组 Subplots\n",
    "# nrows=1, ncols=2 表示创建 1 行 2 列的子图\n",
    "# figsize=(10, 5) 设置整个 Figure 的大小\n",
    "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(10, 5))\n",
    "\n",
    "# 第一个子图 (axes[0])\n",
    "axes[0].plot(x, np.sin(x), color='red', label=\"Sine Function\")\n",
    "axes[0].legend(loc='lower left', fontsize='medium')\n",
    "axes[0].set_title(\"Sine Wave\")\n",
    "\n",
    "# 第二个子图 (axes[1])\n",
    "axes[1].plot(x, np.cos(x), color='blue', label=\"Cosine Function\")\n",
    "axes[1].legend(loc='upper left', fontsize='medium')\n",
    "axes[1].set_title(\"Cosine Wave\")\n",
    "\n",
    "plt.tight_layout() # 自动调整子图间距，避免重叠\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "bcb7e286-fd42-4253-a14a-40ce5fbddc20",
   "metadata": {},
   "source": [
    "### OOP风格：创建子图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "70365938-73db-4a3a-b0df-29e569079f22",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "\n",
    "# 创建一个 Figure 对象\n",
    "fig = plt.figure(figsize=(10, 5)) # 设置Figure大小\n",
    "\n",
    "# 添加第一个子图\n",
    "# fig.add_subplot(1, 2, 1) 表示在 1 行 2 列的网格中添加第一个子图\n",
    "ax1 = fig.add_subplot(1, 2, 1)\n",
    "ax1.plot(x, np.sin(x), color='red', label=\"Sine Function\")\n",
    "ax1.legend(loc='lower left', fontsize='medium')\n",
    "ax1.set_title(\"Sine Wave\") # 使用 Axes 对象的方法设置标题\n",
    "\n",
    "# 添加第二个子图\n",
    "# fig.add_subplot(1, 2, 2) 表示在 1 行 2 列的网格中添加第二个子图\n",
    "ax2 = fig.add_subplot(1, 2, 2)\n",
    "ax2.plot(x, np.cos(x), color='blue', label=\"Cosine Function\")\n",
    "ax2.legend(loc='upper left', fontsize='medium')\n",
    "ax2.set_title(\"Cosine Wave\") # 使用 Axes 对象的方法设置标题\n",
    "\n",
    "plt.tight_layout() # 自动调整子图间距，避免重叠\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "5d9ac013-ebcb-4a7b-bade-a099fb6fb973",
   "metadata": {},
   "source": [
    "### 保存图表"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "6c729a14-7c40-496e-8258-7f5505dfd997",
   "metadata": {},
   "outputs": [],
   "source": [
    "import matplotlib.pyplot as plt\n",
    "import numpy as np\n",
    "\n",
    "x = np.linspace(0, 10, 100)\n",
    "\n",
    "# 使用 plt.subplots() 创建一个 Figure 和一组 Subplots\n",
    "# nrows=1, ncols=2 表示创建 1 行 2 列的子图\n",
    "# figsize=(10, 5) 设置整个 Figure 的大小\n",
    "fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(10, 5))\n",
    "\n",
    "# 第一个子图 (axes[0])\n",
    "axes[0].plot(x, np.sin(x), color='red', label=\"Sine Function\")\n",
    "axes[0].legend(loc='lower left', fontsize='medium')\n",
    "axes[0].set_title(\"Sine Wave\")\n",
    "\n",
    "# 第二个子图 (axes[1])\n",
    "axes[1].plot(x, np.cos(x), color='blue', label=\"Cosine Function\")\n",
    "axes[1].legend(loc='upper left', fontsize='medium')\n",
    "axes[1].set_title(\"Cosine Wave\")\n",
    "\n",
    "# 保存为PNG格式，dpi为分辨率\n",
    "plt.savefig(\"my_plot.png\", dpi=300, bbox_inches='tight')\n",
    "\n",
    "# 保存为PDF格式（矢量图，无损缩放）\n",
    "plt.savefig(\"my_plot.pdf\", bbox_inches='tight')\n",
    "\n",
    "plt.tight_layout() # 自动调整子图间距，避免重叠\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "markdown",
   "id": "b4cd5ffb-5e73-40f2-a60e-6e141f978753",
   "metadata": {},
   "source": [
    "## DataFrame绘图"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "73044999-fe80-4481-b52f-48ce9a7508f5",
   "metadata": {},
   "outputs": [],
   "source": [
    "import pandas as pd\n",
    "import matplotlib.pyplot as plt\n",
    "import numpy as np # 导入numpy，虽然在这个例子中不是严格必需的，但通常会用到\n",
    "\n",
    "# 1. 创建 Pandas DataFrame 数据\n",
    "data = {\n",
    "    '日期': pd.to_datetime(['2025-07-01', '2025-07-02', '2025-07-03', '2025-07-04', '2025-07-05']),\n",
    "    '销售额': [300, 320, 280, 350, 400], # 单位：元\n",
    "    '顾客数量': [50, 55, 45, 60, 70] # 单位：人\n",
    "}\n",
    "df = pd.DataFrame(data)\n",
    "\n",
    "print(\"DataFrame 数据:\")\n",
    "print(df)\n",
    "print(\"-\" * 30)\n",
    "\n",
    "# 2. 使用 Matplotlib 进行绘图\n",
    "# 使用 plt.subplots() 创建一个 Figure 和一组 Subplots，以便更灵活地控制图表\n",
    "fig, ax1 = plt.subplots(figsize=(10, 6)) # 创建一个图和第一个Y轴\n",
    "\n",
    "# 绘制销售额 (左Y轴)\n",
    "color = 'tab:red'\n",
    "ax1.set_xlabel('日期')\n",
    "ax1.set_ylabel('销售额 (元)', color=color)\n",
    "ax1.plot(df['日期'], df['销售额'], color=color, marker='o', label='销售额')\n",
    "ax1.tick_params(axis='y', labelcolor=color)\n",
    "ax1.legend(loc='upper left')\n",
    "ax1.set_title('每日销售额和顾客数量趋势') # 设置图表总标题\n",
    "\n",
    "# 创建第二个Y轴，共享X轴\n",
    "ax2 = ax1.twinx()\n",
    "color = 'tab:blue'\n",
    "ax2.set_ylabel('顾客数量 (人)', color=color)\n",
    "ax2.plot(df['日期'], df['顾客数量'], color=color, marker='x', linestyle='--', label='顾客数量')\n",
    "ax2.tick_params(axis='y', labelcolor=color)\n",
    "ax2.legend(loc='upper right')\n",
    "\n",
    "# 自动调整日期标签，避免重叠\n",
    "fig.autofmt_xdate()\n",
    "\n",
    "plt.tight_layout() # 自动调整子图参数，使之填充整个图像区域\n",
    "plt.show()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "id": "8c61566c-0fe8-4331-aa6e-33a42cd340ec",
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3 (ipykernel)",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.12.11"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 5
}
